package com.shootingGame.mapClasses
{
	
	import com.common.dataStructures2.Array2;
	import com.shootingGame.physics.collisionReactionClasses.base.CollisionEffects;
	import com.shootingGame.renderableClasses.GameObject;
	
	import flash.display.BitmapData;
	import flash.display.Graphics;
	import flash.display.MovieClip;
	import flash.geom.Point;
	import flash.geom.Rectangle;
	
	//GamePlay will instantiate a new Map on map load and pass in the tileset and respective dimensions.
	public class Map
	{
		private var _title:String;
		private var _mapWidth : int;
		private var _mapHeight : int;
		private var _tileData : Array2;
		//Gets an array of tileObjects representing each of the different tiles in a given tile set.
		private var _tileObjects : Array;
		private var _tileWidth : Number;
		private var _tileHeight : Number;
		public var displayMap : MovieClip;
		public var miniMap : MovieClip;
		
		public function Map(title:String, numTilesHorizontal:int, numTilesVertical:int, tileWidth : Number, tileHeight : Number, tileData : Array2, tileSet : TileSet)
		{
			_title = title;
			_mapWidth = numTilesHorizontal * tileWidth;
			_mapHeight = numTilesVertical * tileHeight;
			_tileWidth = tileWidth;
			_tileHeight = tileHeight;
			_tileData = tileData;
			loadTileObjects(tileSet);
			generateBitmap();
		}
		
		
		
		//Copies the children of the TileSet movieclip into an array for faster access.
		public function loadTileObjects(tileSet:TileSet) : void {
			var i : int;
			var n : int = tileSet.numChildren;
			var tileObj:TileObject;
			var wallCollisionEffects : CollisionEffects;			
			_tileObjects = new Array();
			for(i = 0; i < n; i++) {
				tileObj = tileSet.getTileObject(i);
				_tileObjects.push(tileObj);
			}
		}
		
		//Creates a movieclip painted with a bitmap of the entire game map.
		public function generateBitmap() : void {
			var tileId : int;
			var fullBitmapData:BitmapData = new BitmapData(_mapWidth, _mapHeight, false);
			var bitmapData:BitmapData;
			var sourceRect : Rectangle = new Rectangle(0, 0, _tileWidth, _tileHeight);
			var destinationPoint : Point = new Point();
			var row:Array;
			var i : int;
			var j : int;
			var tmpDisp:MovieClip;
			var displayGraphics :Graphics;
			displayMap = new MovieClip();
			for(i = 0; i < _mapHeight / _tileHeight; i++) {
//				row = _tileData.getRow(i);
				for(j = 0; j < _mapWidth / _tileWidth; j++) {
					//tileId = (_tileData[j + (_mapWidth/_tileWidth * i)]) as int;
					tileId = _tileData.getElement(j, i) as int;
//					trace(tileId);
					bitmapData = new BitmapData(_tileWidth, _tileHeight, false);
					bitmapData.draw((tileObjects[tileId] as MovieClip));
					fullBitmapData.merge(bitmapData, sourceRect, destinationPoint,256,256,256,256);
					destinationPoint.x += _tileWidth;
				}
				destinationPoint.x = 0;
				destinationPoint.y += _tileHeight;
			}
			
			displayGraphics = displayMap.graphics;			
			displayGraphics.beginBitmapFill(fullBitmapData);
			displayGraphics.moveTo(0,0);
			displayGraphics.lineTo(0, mapHeight);			
			displayGraphics.lineTo(_mapWidth, _mapHeight);
			displayGraphics.lineTo(_mapWidth, 0);
			displayGraphics.lineTo(0, 0);
			displayGraphics.endFill();
		}
		
		//Checks what tile(s) the game object is positioned on performs any custom reactions.
		public function setTileBlockEffects(gameObject:GameObject) : void {
			var collidablePart:MovieClip = gameObject.getCollidablePart();
			var xUnit:Number = gameObject.memoryX / _tileWidth;
			var yUnit:Number = gameObject.memoryY / _tileHeight;
		}
		


        public function get title() : String
        {
            return title;
        }		
		
		public function get mapWidth() : int{
			return _mapWidth;
		}
		
		public function get mapHeight() : int{
			return _mapHeight;
		}
		
		public function get tileData() : Array2{
			return _tileData;
		}
		
		public function set tileData(value : Array2) {
			_tileData = value;
		}
		
		//Gets an array of tileObjects representing each of the different tiles in a given tile set.
		public function get tileObjects() : Array{
			return _tileObjects;
		}
		
		public function get numTilesHorizontal():int{
			return _tileData.numColumns;
		}
		
		public function get numTilesVertical():int{
			return _tileData.numRows;
		}
		
		public function get tileWidth():Number{
			return _tileWidth;
		}
		
		public function get tileHeight():Number{
			return _tileHeight;
		}

	}
}